#ifndef MESHMANAGER_CPP
#define MESHMANAGER_CPP

//TODO break all this managers in their own file in a new folder called manager

#include "manager.h"

void CMeshManager::changeDrawingType(const ogl::CDrawingType::eBehaviour& eType)
{
    std::map<std::string,CMeshObj>::iterator it;
    for ( it=m_mesh_map.begin() ; it != m_mesh_map.end(); it++ ) (*it).second.changeDrawingType(eType);
}

GLuint CMeshManager::createBoxDisplayList(const Vector3d& center)
{
    GLuint box = glGenLists(1);
    glNewList(box,GL_COMPILE);
        glBegin( GL_QUADS);
            //première face ( Y +)
            glNormal3d(0,1,0);
            glTexCoord2f(1,1);  glVertex3d(center.X-0.5,center.Y+0.5,center.Z-0.5);
            glTexCoord2f(0,1);  glVertex3d(center.X+0.5,center.Y+0.5,center.Z-0.5);
            glTexCoord2f(0,0);  glVertex3d(center.X+0.5,center.Y+0.5,center.Z+0.5);
            glTexCoord2f(1,0);  glVertex3d(center.X-0.5,center.Y+0.5,center.Z+0.5);
            //troisième face ( X - )
            glNormal3d(-1,0,0);
            glTexCoord2d(0,0);  glVertex3d(center.X-0.5,center.Y+0.5,center.Z+0.5);
            glTexCoord2d(0,1);  glVertex3d(center.X-0.5,center.Y+0.5,center.Z-0.5);
            glTexCoord2d(1,1);  glVertex3d(center.X-0.5,center.Y-0.5,center.Z-0.5);
            glTexCoord2d(1,0);  glVertex3d(center.X-0.5,center.Y-0.5,center.Z+0.5);
            //quatrième face ( Z - )
            glNormal3d(0,0,-1);
            glTexCoord2d(1,1);  glVertex3d(center.X-0.5,center.Y+0.5,center.Z-0.5);
            glTexCoord2d(0,1);  glVertex3d(center.X+0.5,center.Y+0.5,center.Z-0.5);
            glTexCoord2d(0,0);  glVertex3d(center.X+0.5,center.Y-0.5,center.Z-0.5);
            glTexCoord2d(1,0);  glVertex3d(center.X-0.5,center.Y-0.5,center.Z-0.5);
            //cinquième face ( Y -)
            glNormal3d(0,-1,0);
            glTexCoord2d(0,1);  glVertex3d(center.X-0.5,center.Y-0.5,center.Z-0.5);
            glTexCoord2d(1,1);  glVertex3d(center.X+0.5,center.Y-0.5,center.Z-0.5);
            glTexCoord2d(1,0);  glVertex3d(center.X+0.5,center.Y-0.5,center.Z+0.5);
            glTexCoord2d(0,0);  glVertex3d(center.X-0.5,center.Y-0.5,center.Z+0.5);
            //sixième face ( X + )
            glNormal3d(1,0,0);
            glTexCoord2d(0,1);  glVertex3d(center.X+0.5,center.Y-0.5,center.Z-0.5);
            glTexCoord2d(1,1);  glVertex3d(center.X+0.5,center.Y+0.5,center.Z-0.5);
            glTexCoord2d(1,0);  glVertex3d(center.X+0.5,center.Y+0.5,center.Z+0.5);
            glTexCoord2d(0,0);  glVertex3d(center.X+0.5,center.Y-0.5,center.Z+0.5);
        glEnd();
    glEndList();
    return box;
}

CMeshObj* CMeshManager::getMeshPtr(const std::string& mesh_name)
{
    return &m_mesh_map.find(mesh_name)->second;
}

void CMeshManager::loadAllMesh()
{
    m_mesh_map["CPlayer"]=CMeshObj();
    m_mesh_map.find("CPlayer")->second.loadObj("blender/seamed_suzanne.obj");
    m_mesh_map["snake"]=CMeshObj();
    m_mesh_map.find("snake")->second.loadObj("blender/pruzina.obj");
}

#endif //MESHMANAGER_CPP

#ifndef TEXTUREMANAGER_CPP
#define TEXTUREMANAGER_CPP

#include "manager.h"

CTextureManager::CTextureManager()
{
}

CTextureManager::~CTextureManager()
{
}

void CTextureManager::loadAllTexture()
{
    std::cout << "Loading textures..." << std::endl;
    // on se crée une image temporaire
    sf::Image image_tampon;

    if ( !image_tampon.LoadFromFile("img/suzanne.png"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    m_texture_map["CPlayer"] = image_tampon;

    if ( !image_tampon.LoadFromFile("img/pruzina.tga"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    m_texture_map["snake"] = image_tampon;

    if ( !image_tampon.LoadFromFile("img/sky_background.jpg"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    m_texture_map["sky"] = image_tampon;

    if ( !image_tampon.LoadFromFile("img/grass.jpg"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    m_texture_map["ground"] = image_tampon;

    if ( !image_tampon.LoadFromFile("img/star.png"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    m_texture_map["star"] = image_tampon;

    // ICI ON CHARGE LES TEXTURES DES CASES

    if ( !image_tampon.LoadFromFile("img/rock043.jpg"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    map_texture_boxes[2]=image_tampon;

    if ( !image_tampon.LoadFromFile("img/crate21.jpg"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    map_texture_boxes[3]=image_tampon;

    // on charge les texture de la case dans la map
    std::pair<int,int> pair_tampon;

    pair_tampon = std::make_pair(2,0);
    if ( !image_tampon.LoadFromFile("img/checker03.jpg"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    map_texture_tiles[pair_tampon]=image_tampon;

    pair_tampon = std::make_pair(2,1);
    if ( !image_tampon.LoadFromFile("img/sand010.jpg"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    map_texture_tiles[pair_tampon]=image_tampon;

    pair_tampon = std::make_pair(3,0);
    if ( !image_tampon.LoadFromFile("img/tiles_ctf01_2.jpg"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    map_texture_tiles[pair_tampon]=image_tampon;

    pair_tampon = std::make_pair(3,1);
    if ( !image_tampon.LoadFromFile("img/tiles_ctf02b.jpg"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    map_texture_tiles[pair_tampon]=image_tampon;

    pair_tampon = std::make_pair(3,2);
    if ( !image_tampon.LoadFromFile("img/tiles_ctf02r.jpg"))
        std::cerr << "N'a pas pu charger la texture" << std::endl;
    map_texture_tiles[pair_tampon]=image_tampon;

    std::cout << "Textures loaded!" << std::endl;
}

void CTextureManager::bindTexture(const std::string& mesh_name)
{
    m_texture_map.find(mesh_name)->second.Bind();
}

#endif //TEXTUREMANAGER_CPP

#ifndef SOUNDMANAGER_CPP
#define SOUNDMANAGER_CPP

#include "manager.h"

CSoundManager::CSoundManager()
{
#ifdef SOUND_ENABLE
    const char * melody[11] = {"do","do","do","re","mi2","re","do","mi2","re","re","do"};
    for (int i=0; i<11; i++)
    {
        m_auclairdelalune.push_back(melody[i]);
    }
    free(melody);
#endif
}

CSoundManager::~CSoundManager()
{
}

void CSoundManager::loadAllBuffer()
{
#ifdef SOUND_ENABLE
    std::cout << "Loading sounds..." << std::endl;
    // chargement des buffers

    sf::SoundBuffer buffer_tampon; // !!

    if (!buffer_tampon.LoadFromFile("snd/do.wav"))
        std::cerr << "N'a pas pu charger le son" << std::endl;
    m_buffer_map["do"] = buffer_tampon;

    if (!buffer_tampon.LoadFromFile("snd/re.wav"))
        std::cerr << "N'a pas pu charger le son" << std::endl;
    m_buffer_map["re"] = buffer_tampon;

    if (!buffer_tampon.LoadFromFile("snd/mi2.wav"))
        std::cerr << "N'a pas pu charger le son" << std::endl;
    m_buffer_map["mi2"] = buffer_tampon;

    if (!buffer_tampon.LoadFromFile("snd/fa.wav"))
        std::cerr << "N'a pas pu charger le son" << std::endl;
    m_buffer_map["fa"] = buffer_tampon;

    if (!buffer_tampon.LoadFromFile("snd/worms/laugh.wav"))
        std::cerr << "N'a pas pu charger le son" << std::endl;
    m_buffer_map["victory"] = buffer_tampon;

    if (!buffer_tampon.LoadFromFile("snd/worms/youllregretthat.wav"))
        std::cerr << "N'a pas pu charger le son" << std::endl;
    m_buffer_map["eaten"] = buffer_tampon;

    // chargement de la musique
    if (!m_music.OpenFromFile("snd/intro.ogg"))
        std::cerr << "N'a pas pu charger le son" << std::endl;

    std::cout << "Sounds loaded!" << std::endl;
#endif
}

void CSoundManager::pauseMusic()
{
#ifdef SOUND_ENABLE
    m_music.Pause();
#endif
}

void CSoundManager::play(const std::string& buffer_name)
{
#ifdef SOUND_ENABLE
    m_sound1.Stop();
    m_sound1.SetBuffer(m_buffer_map.find(buffer_name)->second);
    m_sound1.Play();
#endif
}

void CSoundManager::play(int n)
{
#ifdef SOUND_ENABLE
    n = n%11;
    play(m_auclairdelalune[n]);
#endif
}

void CSoundManager::playMusic()
{
#ifdef SOUND_ENABLE
    if ( m_music.GetStatus() != sf::Music::Playing ) m_music.Play();
#endif
}

void CSoundManager::stopMusic()
{
#ifdef SOUND_ENABLE
    m_music.Stop();
#endif
}

#endif //SOUNDMANAGER_CPP
